package DFGA;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Random;
import java.util.UUID;

import DFGA.population.DFGAPopu;
import abstractGA.AbsGAAlg;
import abstractGA.OutGAResultThread;
import abstractGA.OutPopuThread;
import abstractGA.PopuData;
import abstractGA.chrom.Chrom;
import abstractGA.popu.PopuBuilder;
import algorithm.AlgCtx;
import control.CtrlEngine;
import control.ExeCtx;
import control.PerfEvaluator;
import control.SASolver;
import foundation.concurrency.Product;
import foundation.fileUtil.DataCell;
import foundation.fileUtil.ExcelUtil;

public class DFGAAlg extends AbsGAAlg {
	private Random random = new Random();
	public DFGAAlg(PopuBuilder popuBld) {
		super(popuBld);
	}

	@Override
	public void run(AlgCtx algCtx, int runNum, String rltExlFileNm) {
		//������������������������������
		SimpleDateFormat startDate = new SimpleDateFormat("yyyy-MM-dd_kk-mm-ss");
		String startTime = startDate.format(new Date());
		
		ArrayList<String> runIDs = new ArrayList<String>();
		// ���������������������excel���������������
		for (int i = 1; i <= runNum; i++) {
			// ���������������
			init(algCtx);
			// ������������������
			int maxIterNum = parameter.getMaxIterNum();
			
			//���������������������������������������������������������������������
			
			UUID uuid = UUID.randomUUID();//
			String runID = algCtx.getAlgName() + uuid.toString();
			runIDs.add(runID);

			System.out.println("���������" + i + "���������������.......");
			int genNum = 1;// ������������
			// ������������������������������������������������
			curPopu.getBestChroms();
			// outPopuToDB(algCtx, runID, String.valueOf(genNum), curPopu);
			while (genNum <= maxIterNum) {
				// ������������������
				DFGAPopu nxtPopu = (DFGAPopu) curPopu.copy();
				/**
				 * ���������������������������������������������������������������������������������������������������������������
				 */
				try {
					nxtPopu.geneticOpt();
				} catch (Exception e) {
					e.printStackTrace();
				}
				System.out.println(nxtPopu.toString());
				//���������������������
				curPopu = nxtPopu;
				// ������������
				// ������������������������
				genNum++;
			}
			//������������������������������������������������
//			System.out.println("������������" + genNum + "���������������������" + bestChrom.outChrom());
		}

		//������������������������������
		SimpleDateFormat endDate = new SimpleDateFormat("yyyy-MM-dd_kk-mm-ss");
		String endTime = endDate.format(new Date());
		// ������.xls������
		rltExlFileNm = rltExlFileNm + "_startTime=" + startTime + "_endTime=" + endTime + ".xls";
		// ���������������������excel������
//		MLearnTbl mltbl = MLearnTbl.getInstance();
//
//		CtrlEngine ctrlEngine = (CtrlEngine) algCtx.getAlgOper();
//		completionPerfTbl(mltbl.getPerfSamTbl(), ctrlEngine);
//		int size = runIDs.size();
//		mltbl.outPerfTblToDB(runIDs.get(size - 1));// qing xiao bin xu gai
//		List<List<DataCell>> perfSMQul = mltbl.outPerfSMQul(runIDs.get(size - 1), host, caseName, algNm);
//		// String path = FileNameUtil.getPrjPath();
//		// path = path+"demo\\jssbrs\\runFiles\\resultFiles\\perfSMQul.xls";
//		ExcelUtil.write(rltExlFileNm, perfSMQul);
//		mltbl.clearML();
		List<List<DataCell>> perfSMQul = new ArrayList<List<DataCell>>();
		for (int j = 0; j<curPopu.getChroms().size(); j++) {
			List<DataCell> liDataCells = new ArrayList<>();
			DataCell dataCell1 = new DataCell();
			dataCell1.setName(curPopu.getChroms().get(j).getCodes().toString().trim());
			DataCell dataCell2 = new DataCell();
			dataCell2.setName(curPopu.getChroms().get(j).getObjVals().get(0).toString().trim());
			DataCell dataCell3 = new DataCell();
			dataCell3.setName(curPopu.getChroms().get(j).getObjVals().get(1).toString().trim());
			liDataCells.add(dataCell1);
			liDataCells.add(dataCell2);
			liDataCells.add(dataCell3);
			perfSMQul.add(liDataCells);
		}
		ExcelUtil.write(rltExlFileNm, perfSMQul);

	}

	/**
	 * ������������������������������
	 * 
	 * @param curMutFactor���������������������
	 * @param mutFactors������������������������������
	 * @return
	 */
	public float getNxtMutFactor(float curMutFactor, List<Float> mutFactors) {
		float nxtMutFactor = 0f;
		if (mutFactors.size() > 0) {
			float coef = ((DFGAParameter) parameter).getCoef();
			float sum = 0f;
			float sqSum = 0f;
			for (Float factor : mutFactors) {
				sum += factor;
				sqSum += factor * factor;
			}

			nxtMutFactor = (1f - coef) * curMutFactor + coef * (sqSum / sum);
		}
		return nxtMutFactor;
	}

	/**
	 * ������������������������������
	 * 
	 * @param curCrob������������������������
	 * @param crobs������������������������������
	 * @return
	 */
	public float getNxtCrob(float curCrob, List<Float> crobs) {
		float nxtCrob = 0f;
		int size = crobs.size();
		if (size > 0) {
			float coef = ((DFGAParameter) parameter).getCoef();
			float sum = 0f;
			for (Float crob : crobs) {
				sum += crob;
			}

			nxtCrob = (1f - coef) * curCrob + coef * (sum / size);
		}
		return nxtCrob;
	}

	public static void main(String[] args) {

		for (int i = 0; i < 10; i++) {
			UUID uuid = UUID.randomUUID();
			String uuidStr = uuid.toString();
			System.out.println(uuidStr + ":" + uuidStr);
		}
	}
}
